package com.gy.hadoop.juc.cas_;

import java.util.concurrent.atomic.AtomicInteger;

/*
CAS是指**Compare And Swap**，**比较并交换**，是一种很重要的同步思想。如果主内存的值跟期望值一样，那么就进行修改，否则一直重试，直到一致为止。

CAS实际上是一种自旋锁，
    1. 一直循环，开销比较大。    --Longadder
    2. 只能保证一个变量的原子操作，多个变量依然要加锁。 --
        User user1 = new User("Jack",25);
        User user2 = new User("Lucy",21);
        AtomicReference<User> atomicReference = new AtomicReference<>();
        atomicReference.set(user1);
        System.out.println(atomicReference.compareAndSet(user1,user2)); // true
        System.out.println(atomicReference.compareAndSet(user1,user2)); //false
    3. 引出了**ABA问题**。 --AtomicStampedReference 设置一个版本号（CAS操作比较指&&比较版本号）
        AtomicStampedReference.compareAndSet(expectedReference,newReference,oldStamp,newStamp);
集合不安全问题
List：
    1. 使用`Vector`（`ArrayList`所有方法加`synchronized`，太重）。
    2. 使用`Collections.synchronizedList()`转换成线程安全类。
    3. 使用`java.concurrent.CopyOnWriteArrayList`（推荐 写时复制读写分离【加锁--复制出len+1数据，给len位置赋值返回新数组】）。
Set（HashSet，treeSet）：
    跟List类似线程不安全问题问题
    使用`CopyOnWriteSet`（推荐 装饰模式包装一层CopyOnWriteArrayList【底层维护了一个`CopyOnWriteArrayList`数组】）
HashSet和HashMap：
    `HashSet`底层是用`HashMap`实现的（value被固定为一个object对象）
Map：
    Hashtable`是线程安全的，但是跟`Vector`类似，太重量级
    推荐使用`ConcurrentHashMap`  锁分段 8段
 */
public class CasDemo {

    public static void main(String[] args) {
        AtomicInteger atomicInteger = new AtomicInteger(5);
        System.out.println(atomicInteger.compareAndSet(5, 2019) + "\t current data : " + atomicInteger.get());
        //修改失败
        System.out.println(atomicInteger.compareAndSet(5, 1024) + "\t current data : " + atomicInteger.get());
    }



}
